﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.IO;
using ICSharpCode.SharpZipLib.Zip;
using ICSharpCode.SharpZipLib.Checksums;
/*
 调用示例
 *        string[] files = { Server.MapPath("/Files/记事本.mp3"), Server.MapPath("/Files/StyleSheet1.txt") };
          SharpZipLibHelper.ZipFileMain(files, Server.MapPath("/Files") + @"/备份的压缩数据.zip", 9);
/*
 NickName:Irving
 Email:zhouyontao@outlook.com
 Date:2012年9月10日16:23:08
 */
namespace Common
{
    public class SharpZipLibHelper
    {

        /// <summary>
        /// 压缩文件
        /// </summary>
        /// <param name="fileName">要压缩的所有文件（完全路径)</param>
        /// <param name="name">压缩后文件路径</param>
        /// <param name="Level">压缩级别0-9</param>
        public static void ZipFileMain(string[] filenames, string name, int level)
        {
            ZipOutputStream s = new ZipOutputStream(File.Create(name));
            Crc32 crc = new Crc32();
            //压缩级别
            s.SetLevel(level); // 0 - store only to 9 - means best compression
            try
            {
                foreach (string file in filenames)
                {
                    //打开压缩文件
                    FileStream fs = File.OpenRead(file);

                    byte[] buffer = new byte[fs.Length];
                    fs.Read(buffer, 0, buffer.Length);

                    //建立压缩实体
                    ZipEntry entry = new ZipEntry(System.IO.Path.GetFileName(file));

                    //时间
                    entry.DateTime = DateTime.Now;

                    // set Size and the crc, because the information
                    // about the size and crc should be stored in the header
                    // if it is not set it is automatically written in the footer.
                    // (in this case size == crc == -1 in the header)
                    // Some ZIP programs have problems with zip files that don't store
                    // the size and crc in the header.
                    //空间大小
                    entry.Size = fs.Length;
                    fs.Close();
                    crc.Reset();
                    crc.Update(buffer);
                    entry.Crc = crc.Value;
                    s.PutNextEntry(entry);
                    s.Write(buffer, 0, buffer.Length);
                }
            }
            catch
            {
                throw;
            }
            finally
            {
                s.Finish();
                s.Close();
            }

        }


        /// <summary>
        /// 解压文件
        /// </summary>
        /// <param name="zipPath">被解压的文件路径</param>
        /// <param name="Path">解压后文件的路径</param>
        public static void UnZip(string zipPath, string path)
        {
            ZipInputStream s = new ZipInputStream(File.OpenRead(zipPath));

            ZipEntry theEntry;
            try
            {
                while ((theEntry = s.GetNextEntry()) != null)
                {
                    string fileName = System.IO.Path.GetFileName(theEntry.Name);

                    //生成解压目录
                    Directory.CreateDirectory(path);

                    if (fileName != String.Empty)
                    {
                        //解压文件
                        FileStream streamWriter = File.Create(path + fileName);

                        int size = 2048;
                        byte[] data = new byte[2048];
                        while (true)
                        {
                            size = s.Read(data, 0, data.Length);
                            if (size > 0)
                            {
                                streamWriter.Write(data, 0, size);
                            }
                            else
                            {

                                streamWriter.Close();
                                streamWriter.Dispose();
                                break;
                            }
                        }

                        streamWriter.Close();
                        streamWriter.Dispose();
                    }
                }
            }
            catch
            {
                throw;
            }
            finally
            {
                s.Close();
                s.Dispose();
            }
        }
    }
}

